1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package com.google.common.collect;
18
19 import static com.google.common.base.Preconditions.checkArgument;
20 import static com.google.common.base.Preconditions.checkNotNull;
21 import static com.google.common.collect.CollectPreconditions.checkNonnegative;
22 import static com.google.common.collect.CollectPreconditions.checkRemove;
23
24 import com.google.common.annotations.Beta;
25 import com.google.common.annotations.GwtCompatible;
26 import com.google.common.base.Objects;
27 import com.google.common.base.Predicate;
28 import com.google.common.base.Predicates;
29 import com.google.common.collect.Multiset.Entry;
30 import com.google.common.primitives.Ints;
31
32 import java.io.Serializable;
33 import java.util.Collection;
34 import java.util.Collections;
35 import java.util.Iterator;
36 import java.util.List;
37 import java.util.NoSuchElementException;
38 import java.util.Set;
39
40 import javax.annotation.Nullable;
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55 @GwtCompatible
56 public final class Multisets {
57 private Multisets() {}
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72 public static <E> Multiset<E> unmodifiableMultiset(
73 Multiset<? extends E> multiset) {
74 if (multiset instanceof UnmodifiableMultiset ||
75 multiset instanceof ImmutableMultiset) {
76
77 @SuppressWarnings("unchecked")
78 Multiset<E> result = (Multiset<E>) multiset;
79 return result;
80 }
81 return new UnmodifiableMultiset<E>(checkNotNull(multiset));
82 }
83
84
85
86
87
88
89
90 @Deprecated public static <E> Multiset<E> unmodifiableMultiset(
91 ImmutableMultiset<E> multiset) {
92 return checkNotNull(multiset);
93 }
94
95 static class UnmodifiableMultiset<E>
96 extends ForwardingMultiset<E> implements Serializable {
97 final Multiset<? extends E> delegate;
98
99 UnmodifiableMultiset(Multiset<? extends E> delegate) {
100 this.delegate = delegate;
101 }
102
103 @SuppressWarnings("unchecked")
104 @Override protected Multiset<E> delegate() {
105
106 return (Multiset<E>) delegate;
107 }
108
109 transient Set<E> elementSet;
110
111 Set<E> createElementSet() {
112 return Collections.<E>unmodifiableSet(delegate.elementSet());
113 }
114
115 @Override
116 public Set<E> elementSet() {
117 Set<E> es = elementSet;
118 return (es == null) ? elementSet = createElementSet() : es;
119 }
120
121 transient Set<Multiset.Entry<E>> entrySet;
122
123 @SuppressWarnings("unchecked")
124 @Override public Set<Multiset.Entry<E>> entrySet() {
125 Set<Multiset.Entry<E>> es = entrySet;
126 return (es == null)
127
128
129 ? entrySet = (Set) Collections.unmodifiableSet(delegate.entrySet())
130 : es;
131 }
132
133 @SuppressWarnings("unchecked")
134 @Override public Iterator<E> iterator() {
135
136 return (Iterator<E>) Iterators.unmodifiableIterator(delegate.iterator());
137 }
138
139 @Override public boolean add(E element) {
140 throw new UnsupportedOperationException();
141 }
142
143 @Override public int add(E element, int occurences) {
144 throw new UnsupportedOperationException();
145 }
146
147 @Override public boolean addAll(Collection<? extends E> elementsToAdd) {
148 throw new UnsupportedOperationException();
149 }
150
151 @Override public boolean remove(Object element) {
152 throw new UnsupportedOperationException();
153 }
154
155 @Override public int remove(Object element, int occurrences) {
156 throw new UnsupportedOperationException();
157 }
158
159 @Override public boolean removeAll(Collection<?> elementsToRemove) {
160 throw new UnsupportedOperationException();
161 }
162
163 @Override public boolean retainAll(Collection<?> elementsToRetain) {
164 throw new UnsupportedOperationException();
165 }
166
167 @Override public void clear() {
168 throw new UnsupportedOperationException();
169 }
170
171 @Override public int setCount(E element, int count) {
172 throw new UnsupportedOperationException();
173 }
174
175 @Override public boolean setCount(E element, int oldCount, int newCount) {
176 throw new UnsupportedOperationException();
177 }
178
179 private static final long serialVersionUID = 0;
180 }
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196 @Beta
197 public static <E> SortedMultiset<E> unmodifiableSortedMultiset(
198 SortedMultiset<E> sortedMultiset) {
199
200 return new UnmodifiableSortedMultiset<E>(checkNotNull(sortedMultiset));
201 }
202
203
204
205
206
207
208
209
210
211 public static <E> Multiset.Entry<E> immutableEntry(@Nullable E e, int n) {
212 return new ImmutableEntry<E>(e, n);
213 }
214
215 static final class ImmutableEntry<E> extends AbstractEntry<E> implements
216 Serializable {
217 @Nullable final E element;
218 final int count;
219
220 ImmutableEntry(@Nullable E element, int count) {
221 this.element = element;
222 this.count = count;
223 checkNonnegative(count, "count");
224 }
225
226 @Override
227 @Nullable public E getElement() {
228 return element;
229 }
230
231 @Override
232 public int getCount() {
233 return count;
234 }
235
236 private static final long serialVersionUID = 0;
237 }
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265 @Beta
266 public static <E> Multiset<E> filter(Multiset<E> unfiltered, Predicate<? super E> predicate) {
267 if (unfiltered instanceof FilteredMultiset) {
268
269
270 FilteredMultiset<E> filtered = (FilteredMultiset<E>) unfiltered;
271 Predicate<E> combinedPredicate
272 = Predicates.<E>and(filtered.predicate, predicate);
273 return new FilteredMultiset<E>(filtered.unfiltered, combinedPredicate);
274 }
275 return new FilteredMultiset<E>(unfiltered, predicate);
276 }
277
278 private static final class FilteredMultiset<E> extends AbstractMultiset<E> {
279 final Multiset<E> unfiltered;
280 final Predicate<? super E> predicate;
281
282 FilteredMultiset(Multiset<E> unfiltered, Predicate<? super E> predicate) {
283 this.unfiltered = checkNotNull(unfiltered);
284 this.predicate = checkNotNull(predicate);
285 }
286
287 @Override
288 public UnmodifiableIterator<E> iterator() {
289 return Iterators.filter(unfiltered.iterator(), predicate);
290 }
291
292 @Override
293 Set<E> createElementSet() {
294 return Sets.filter(unfiltered.elementSet(), predicate);
295 }
296
297 @Override
298 Set<Entry<E>> createEntrySet() {
299 return Sets.filter(unfiltered.entrySet(), new Predicate<Entry<E>>() {
300 @Override
301 public boolean apply(Entry<E> entry) {
302 return predicate.apply(entry.getElement());
303 }
304 });
305 }
306
307 @Override
308 Iterator<Entry<E>> entryIterator() {
309 throw new AssertionError("should never be called");
310 }
311
312 @Override
313 int distinctElements() {
314 return elementSet().size();
315 }
316
317 @Override
318 public int count(@Nullable Object element) {
319 int count = unfiltered.count(element);
320 if (count > 0) {
321 @SuppressWarnings("unchecked")
322 E e = (E) element;
323 return predicate.apply(e) ? count : 0;
324 }
325 return 0;
326 }
327
328 @Override
329 public int add(@Nullable E element, int occurrences) {
330 checkArgument(predicate.apply(element),
331 "Element %s does not match predicate %s", element, predicate);
332 return unfiltered.add(element, occurrences);
333 }
334
335 @Override
336 public int remove(@Nullable Object element, int occurrences) {
337 checkNonnegative(occurrences, "occurrences");
338 if (occurrences == 0) {
339 return count(element);
340 } else {
341 return contains(element) ? unfiltered.remove(element, occurrences) : 0;
342 }
343 }
344
345 @Override
346 public void clear() {
347 elementSet().clear();
348 }
349 }
350
351
352
353
354
355
356
357 static int inferDistinctElements(Iterable<?> elements) {
358 if (elements instanceof Multiset) {
359 return ((Multiset<?>) elements).elementSet().size();
360 }
361 return 11;
362 }
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379 @Beta
380 public static <E> Multiset<E> union(
381 final Multiset<? extends E> multiset1, final Multiset<? extends E> multiset2) {
382 checkNotNull(multiset1);
383 checkNotNull(multiset2);
384
385 return new AbstractMultiset<E>() {
386 @Override
387 public boolean contains(@Nullable Object element) {
388 return multiset1.contains(element) || multiset2.contains(element);
389 }
390
391 @Override
392 public boolean isEmpty() {
393 return multiset1.isEmpty() && multiset2.isEmpty();
394 }
395
396 @Override
397 public int count(Object element) {
398 return Math.max(multiset1.count(element), multiset2.count(element));
399 }
400
401 @Override
402 Set<E> createElementSet() {
403 return Sets.union(multiset1.elementSet(), multiset2.elementSet());
404 }
405
406 @Override
407 Iterator<Entry<E>> entryIterator() {
408 final Iterator<? extends Entry<? extends E>> iterator1
409 = multiset1.entrySet().iterator();
410 final Iterator<? extends Entry<? extends E>> iterator2
411 = multiset2.entrySet().iterator();
412
413 return new AbstractIterator<Entry<E>>() {
414 @Override
415 protected Entry<E> computeNext() {
416 if (iterator1.hasNext()) {
417 Entry<? extends E> entry1 = iterator1.next();
418 E element = entry1.getElement();
419 int count = Math.max(entry1.getCount(), multiset2.count(element));
420 return immutableEntry(element, count);
421 }
422 while (iterator2.hasNext()) {
423 Entry<? extends E> entry2 = iterator2.next();
424 E element = entry2.getElement();
425 if (!multiset1.contains(element)) {
426 return immutableEntry(element, entry2.getCount());
427 }
428 }
429 return endOfData();
430 }
431 };
432 }
433
434 @Override
435 int distinctElements() {
436 return elementSet().size();
437 }
438 };
439 }
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455 public static <E> Multiset<E> intersection(
456 final Multiset<E> multiset1, final Multiset<?> multiset2) {
457 checkNotNull(multiset1);
458 checkNotNull(multiset2);
459
460 return new AbstractMultiset<E>() {
461 @Override
462 public int count(Object element) {
463 int count1 = multiset1.count(element);
464 return (count1 == 0) ? 0 : Math.min(count1, multiset2.count(element));
465 }
466
467 @Override
468 Set<E> createElementSet() {
469 return Sets.intersection(
470 multiset1.elementSet(), multiset2.elementSet());
471 }
472
473 @Override
474 Iterator<Entry<E>> entryIterator() {
475 final Iterator<Entry<E>> iterator1 = multiset1.entrySet().iterator();
476
477 return new AbstractIterator<Entry<E>>() {
478 @Override
479 protected Entry<E> computeNext() {
480 while (iterator1.hasNext()) {
481 Entry<E> entry1 = iterator1.next();
482 E element = entry1.getElement();
483 int count = Math.min(entry1.getCount(), multiset2.count(element));
484 if (count > 0) {
485 return immutableEntry(element, count);
486 }
487 }
488 return endOfData();
489 }
490 };
491 }
492
493 @Override
494 int distinctElements() {
495 return elementSet().size();
496 }
497 };
498 }
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515 @Beta
516 public static <E> Multiset<E> sum(
517 final Multiset<? extends E> multiset1, final Multiset<? extends E> multiset2) {
518 checkNotNull(multiset1);
519 checkNotNull(multiset2);
520
521
522 return new AbstractMultiset<E>() {
523 @Override
524 public boolean contains(@Nullable Object element) {
525 return multiset1.contains(element) || multiset2.contains(element);
526 }
527
528 @Override
529 public boolean isEmpty() {
530 return multiset1.isEmpty() && multiset2.isEmpty();
531 }
532
533 @Override
534 public int size() {
535 return multiset1.size() + multiset2.size();
536 }
537
538 @Override
539 public int count(Object element) {
540 return multiset1.count(element) + multiset2.count(element);
541 }
542
543 @Override
544 Set<E> createElementSet() {
545 return Sets.union(multiset1.elementSet(), multiset2.elementSet());
546 }
547
548 @Override
549 Iterator<Entry<E>> entryIterator() {
550 final Iterator<? extends Entry<? extends E>> iterator1
551 = multiset1.entrySet().iterator();
552 final Iterator<? extends Entry<? extends E>> iterator2
553 = multiset2.entrySet().iterator();
554 return new AbstractIterator<Entry<E>>() {
555 @Override
556 protected Entry<E> computeNext() {
557 if (iterator1.hasNext()) {
558 Entry<? extends E> entry1 = iterator1.next();
559 E element = entry1.getElement();
560 int count = entry1.getCount() + multiset2.count(element);
561 return immutableEntry(element, count);
562 }
563 while (iterator2.hasNext()) {
564 Entry<? extends E> entry2 = iterator2.next();
565 E element = entry2.getElement();
566 if (!multiset1.contains(element)) {
567 return immutableEntry(element, entry2.getCount());
568 }
569 }
570 return endOfData();
571 }
572 };
573 }
574
575 @Override
576 int distinctElements() {
577 return elementSet().size();
578 }
579 };
580 }
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597 @Beta
598 public static <E> Multiset<E> difference(
599 final Multiset<E> multiset1, final Multiset<?> multiset2) {
600 checkNotNull(multiset1);
601 checkNotNull(multiset2);
602
603
604 return new AbstractMultiset<E>() {
605 @Override
606 public int count(@Nullable Object element) {
607 int count1 = multiset1.count(element);
608 return (count1 == 0) ? 0 :
609 Math.max(0, count1 - multiset2.count(element));
610 }
611
612 @Override
613 Iterator<Entry<E>> entryIterator() {
614 final Iterator<Entry<E>> iterator1 = multiset1.entrySet().iterator();
615 return new AbstractIterator<Entry<E>>() {
616 @Override
617 protected Entry<E> computeNext() {
618 while (iterator1.hasNext()) {
619 Entry<E> entry1 = iterator1.next();
620 E element = entry1.getElement();
621 int count = entry1.getCount() - multiset2.count(element);
622 if (count > 0) {
623 return immutableEntry(element, count);
624 }
625 }
626 return endOfData();
627 }
628 };
629 }
630
631 @Override
632 int distinctElements() {
633 return Iterators.size(entryIterator());
634 }
635 };
636 }
637
638
639
640
641
642
643
644 public static boolean containsOccurrences(
645 Multiset<?> superMultiset, Multiset<?> subMultiset) {
646 checkNotNull(superMultiset);
647 checkNotNull(subMultiset);
648 for (Entry<?> entry : subMultiset.entrySet()) {
649 int superCount = superMultiset.count(entry.getElement());
650 if (superCount < entry.getCount()) {
651 return false;
652 }
653 }
654 return true;
655 }
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676 public static boolean retainOccurrences(Multiset<?> multisetToModify,
677 Multiset<?> multisetToRetain) {
678 return retainOccurrencesImpl(multisetToModify, multisetToRetain);
679 }
680
681
682
683
684 private static <E> boolean retainOccurrencesImpl(
685 Multiset<E> multisetToModify, Multiset<?> occurrencesToRetain) {
686 checkNotNull(multisetToModify);
687 checkNotNull(occurrencesToRetain);
688
689 Iterator<Entry<E>> entryIterator = multisetToModify.entrySet().iterator();
690 boolean changed = false;
691 while (entryIterator.hasNext()) {
692 Entry<E> entry = entryIterator.next();
693 int retainCount = occurrencesToRetain.count(entry.getElement());
694 if (retainCount == 0) {
695 entryIterator.remove();
696 changed = true;
697 } else if (retainCount < entry.getCount()) {
698 multisetToModify.setCount(entry.getElement(), retainCount);
699 changed = true;
700 }
701 }
702 return changed;
703 }
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729 public static boolean removeOccurrences(
730 Multiset<?> multisetToModify, Iterable<?> occurrencesToRemove) {
731 if (occurrencesToRemove instanceof Multiset) {
732 return removeOccurrencesImpl(
733 multisetToModify, (Multiset<?>) occurrencesToRemove);
734 } else {
735 return removeOccurrencesImpl(multisetToModify, occurrencesToRemove);
736 }
737 }
738
739 private static boolean removeOccurrencesImpl(
740 Multiset<?> multisetToModify, Iterable<?> occurrencesToRemove) {
741 checkNotNull(multisetToModify);
742 checkNotNull(occurrencesToRemove);
743 boolean changed = false;
744 for (Object o : occurrencesToRemove) {
745 changed |= multisetToModify.remove(o);
746 }
747 return changed;
748 }
749
750
751
752
753 private static <E> boolean removeOccurrencesImpl(
754 Multiset<E> multisetToModify, Multiset<?> occurrencesToRemove) {
755
756 checkNotNull(multisetToModify);
757 checkNotNull(occurrencesToRemove);
758
759 boolean changed = false;
760 Iterator<Entry<E>> entryIterator = multisetToModify.entrySet().iterator();
761 while (entryIterator.hasNext()) {
762 Entry<E> entry = entryIterator.next();
763 int removeCount = occurrencesToRemove.count(entry.getElement());
764 if (removeCount >= entry.getCount()) {
765 entryIterator.remove();
766 changed = true;
767 } else if (removeCount > 0) {
768 multisetToModify.remove(entry.getElement(), removeCount);
769 changed = true;
770 }
771 }
772 return changed;
773 }
774
775
776
777
778
779 abstract static class AbstractEntry<E> implements Multiset.Entry<E> {
780
781
782
783
784 @Override public boolean equals(@Nullable Object object) {
785 if (object instanceof Multiset.Entry) {
786 Multiset.Entry<?> that = (Multiset.Entry<?>) object;
787 return this.getCount() == that.getCount()
788 && Objects.equal(this.getElement(), that.getElement());
789 }
790 return false;
791 }
792
793
794
795
796
797 @Override public int hashCode() {
798 E e = getElement();
799 return ((e == null) ? 0 : e.hashCode()) ^ getCount();
800 }
801
802
803
804
805
806
807
808
809 @Override public String toString() {
810 String text = String.valueOf(getElement());
811 int n = getCount();
812 return (n == 1) ? text : (text + " x " + n);
813 }
814 }
815
816
817
818
819 static boolean equalsImpl(Multiset<?> multiset, @Nullable Object object) {
820 if (object == multiset) {
821 return true;
822 }
823 if (object instanceof Multiset) {
824 Multiset<?> that = (Multiset<?>) object;
825
826
827
828
829
830
831 if (multiset.size() != that.size()
832 || multiset.entrySet().size() != that.entrySet().size()) {
833 return false;
834 }
835 for (Entry<?> entry : that.entrySet()) {
836 if (multiset.count(entry.getElement()) != entry.getCount()) {
837 return false;
838 }
839 }
840 return true;
841 }
842 return false;
843 }
844
845
846
847
848 static <E> boolean addAllImpl(
849 Multiset<E> self, Collection<? extends E> elements) {
850 if (elements.isEmpty()) {
851 return false;
852 }
853 if (elements instanceof Multiset) {
854 Multiset<? extends E> that = cast(elements);
855 for (Entry<? extends E> entry : that.entrySet()) {
856 self.add(entry.getElement(), entry.getCount());
857 }
858 } else {
859 Iterators.addAll(self, elements.iterator());
860 }
861 return true;
862 }
863
864
865
866
867 static boolean removeAllImpl(
868 Multiset<?> self, Collection<?> elementsToRemove) {
869 Collection<?> collection = (elementsToRemove instanceof Multiset)
870 ? ((Multiset<?>) elementsToRemove).elementSet() : elementsToRemove;
871
872 return self.elementSet().removeAll(collection);
873 }
874
875
876
877
878 static boolean retainAllImpl(
879 Multiset<?> self, Collection<?> elementsToRetain) {
880 checkNotNull(elementsToRetain);
881 Collection<?> collection = (elementsToRetain instanceof Multiset)
882 ? ((Multiset<?>) elementsToRetain).elementSet() : elementsToRetain;
883
884 return self.elementSet().retainAll(collection);
885 }
886
887
888
889
890 static <E> int setCountImpl(Multiset<E> self, E element, int count) {
891 checkNonnegative(count, "count");
892
893 int oldCount = self.count(element);
894
895 int delta = count - oldCount;
896 if (delta > 0) {
897 self.add(element, delta);
898 } else if (delta < 0) {
899 self.remove(element, -delta);
900 }
901
902 return oldCount;
903 }
904
905
906
907
908 static <E> boolean setCountImpl(
909 Multiset<E> self, E element, int oldCount, int newCount) {
910 checkNonnegative(oldCount, "oldCount");
911 checkNonnegative(newCount, "newCount");
912
913 if (self.count(element) == oldCount) {
914 self.setCount(element, newCount);
915 return true;
916 } else {
917 return false;
918 }
919 }
920
921 abstract static class ElementSet<E> extends Sets.ImprovedAbstractSet<E> {
922 abstract Multiset<E> multiset();
923
924 @Override public void clear() {
925 multiset().clear();
926 }
927
928 @Override public boolean contains(Object o) {
929 return multiset().contains(o);
930 }
931
932 @Override public boolean containsAll(Collection<?> c) {
933 return multiset().containsAll(c);
934 }
935
936 @Override public boolean isEmpty() {
937 return multiset().isEmpty();
938 }
939
940 @Override public Iterator<E> iterator() {
941 return new TransformedIterator<Entry<E>, E>(multiset().entrySet().iterator()) {
942 @Override
943 E transform(Entry<E> entry) {
944 return entry.getElement();
945 }
946 };
947 }
948
949 @Override
950 public boolean remove(Object o) {
951 int count = multiset().count(o);
952 if (count > 0) {
953 multiset().remove(o, count);
954 return true;
955 }
956 return false;
957 }
958
959 @Override public int size() {
960 return multiset().entrySet().size();
961 }
962 }
963
964 abstract static class EntrySet<E> extends Sets.ImprovedAbstractSet<Entry<E>> {
965 abstract Multiset<E> multiset();
966
967 @Override public boolean contains(@Nullable Object o) {
968 if (o instanceof Entry) {
969
970
971
972 @SuppressWarnings("cast")
973 Entry<?> entry = (Entry<?>) o;
974 if (entry.getCount() <= 0) {
975 return false;
976 }
977 int count = multiset().count(entry.getElement());
978 return count == entry.getCount();
979
980 }
981 return false;
982 }
983
984
985 @SuppressWarnings("cast")
986 @Override public boolean remove(Object object) {
987 if (object instanceof Multiset.Entry) {
988 Entry<?> entry = (Entry<?>) object;
989 Object element = entry.getElement();
990 int entryCount = entry.getCount();
991 if (entryCount != 0) {
992
993 @SuppressWarnings("unchecked")
994 Multiset<Object> multiset = (Multiset) multiset();
995 return multiset.setCount(element, entryCount, 0);
996 }
997 }
998 return false;
999 }
1000
1001 @Override public void clear() {
1002 multiset().clear();
1003 }
1004 }
1005
1006
1007
1008
1009 static <E> Iterator<E> iteratorImpl(Multiset<E> multiset) {
1010 return new MultisetIteratorImpl<E>(
1011 multiset, multiset.entrySet().iterator());
1012 }
1013
1014 static final class MultisetIteratorImpl<E> implements Iterator<E> {
1015 private final Multiset<E> multiset;
1016 private final Iterator<Entry<E>> entryIterator;
1017 private Entry<E> currentEntry;
1018
1019 private int laterCount;
1020
1021 private int totalCount;
1022 private boolean canRemove;
1023
1024 MultisetIteratorImpl(
1025 Multiset<E> multiset, Iterator<Entry<E>> entryIterator) {
1026 this.multiset = multiset;
1027 this.entryIterator = entryIterator;
1028 }
1029
1030 @Override
1031 public boolean hasNext() {
1032 return laterCount > 0 || entryIterator.hasNext();
1033 }
1034
1035 @Override
1036 public E next() {
1037 if (!hasNext()) {
1038 throw new NoSuchElementException();
1039 }
1040 if (laterCount == 0) {
1041 currentEntry = entryIterator.next();
1042 totalCount = laterCount = currentEntry.getCount();
1043 }
1044 laterCount--;
1045 canRemove = true;
1046 return currentEntry.getElement();
1047 }
1048
1049 @Override
1050 public void remove() {
1051 checkRemove(canRemove);
1052 if (totalCount == 1) {
1053 entryIterator.remove();
1054 } else {
1055 multiset.remove(currentEntry.getElement());
1056 }
1057 totalCount--;
1058 canRemove = false;
1059 }
1060 }
1061
1062
1063
1064
1065 static int sizeImpl(Multiset<?> multiset) {
1066 long size = 0;
1067 for (Entry<?> entry : multiset.entrySet()) {
1068 size += entry.getCount();
1069 }
1070 return Ints.saturatedCast(size);
1071 }
1072
1073
1074
1075
1076 static <T> Multiset<T> cast(Iterable<T> iterable) {
1077 return (Multiset<T>) iterable;
1078 }
1079
1080 private static final Ordering<Entry<?>> DECREASING_COUNT_ORDERING = new Ordering<Entry<?>>() {
1081 @Override
1082 public int compare(Entry<?> entry1, Entry<?> entry2) {
1083 return Ints.compare(entry2.getCount(), entry1.getCount());
1084 }
1085 };
1086
1087
1088
1089
1090
1091
1092
1093 @Beta
1094 public static <E> ImmutableMultiset<E> copyHighestCountFirst(Multiset<E> multiset) {
1095 List<Entry<E>> sortedEntries =
1096 Multisets.DECREASING_COUNT_ORDERING.immutableSortedCopy(multiset.entrySet());
1097 return ImmutableMultiset.copyFromEntries(sortedEntries);
1098 }
1099 }